
// <copyright file="PerfCounterHttpListener.cs" company="Subhadra Software Solutions">
//   
// </copyright>
// <summary>
//   The perf counter http listener.
// </summary>

namespace SubhadraSolutions.Sharp.Utils.Diagnostics.Performance
{
    using System.Data;
    using System.IO;
    using System.Net;
    using System.Text;

    using SubhadraSolutions.Sharp.Utils.Data;
    using SubhadraSolutions.Sharp.Utils.Net;
    using SubhadraSolutions.Sharp.Utils.Web;

    /// <summary>
    /// The perf counter http listener.
    /// </summary>
    public sealed class PerfCounterHttpListener : AbstractHttpListenerWrapper
    {
        #region Static Fields

        /// <summary>
        /// The instance.
        /// </summary>
        private static readonly PerfCounterHttpListener InstanceObject = new PerfCounterHttpListener();

        #endregion Static Fields

        #region Constructors and Finalizers

        /// <summary>
        /// Prevents a default instance of the <see cref="PerfCounterHttpListener"/> class from being created.
        /// </summary>
        private PerfCounterHttpListener()
        {
        }

        #endregion Constructors and Finalizers

        #region Public Properties

        /// <summary>
        /// Gets the instance.
        /// </summary>
        public static PerfCounterHttpListener Instance
        {
            get
            {
                return InstanceObject;
            }
        }

        #endregion Public Properties

        #region Methods

        /// <summary>
        /// The process request.
        /// </summary>
        /// <param name="context">
        /// The context.
        /// </param>
        protected override void processRequest(HttpListenerContext context)
        {
            string categoryName = context.Request.QueryString["CategoryName"];

            using (var writer = new StringWriter())
            {
                HtmlExportHelper.WriteStyledHtmlHeader(writer, HtmlExportHelper.TableStyle, HtmlExportHelper.HeaderCellStyle, HtmlExportHelper.NumericCellStyle, HtmlExportHelper.CellStyle, "Performance Counters");
                if (string.IsNullOrWhiteSpace(categoryName))
                {
                    foreach (PerfCounterCategory category in
                        PerfCounterManager.Instance.GetAllCategories())
                    {
                        this.writeCategory(category, writer);
                    }
                }
                else
                {
                    PerfCounterCategory category = PerfCounterManager.Instance.GetCategory(categoryName);
                    if (category != null)
                    {
                        this.writeCategory(category, writer);
                    }
                }

                writer.Write("</body></html>");
                byte[] responseBytes = Encoding.ASCII.GetBytes(writer.ToString());
                context.Response.ContentLength64 = responseBytes.Length;
                context.Response.OutputStream.Write(responseBytes, 0, responseBytes.Length);
                context.Response.ContentType = "text/html";
                context.Response.Close();
            }
        }

        /// <summary>
        /// The write category.
        /// </summary>
        /// <param name="category">
        /// The category.
        /// </param>
        /// <param name="writer">
        /// The writer.
        /// </param>
        private void writeCategory(PerfCounterCategory category, TextWriter writer)
        {
            DataTable table = category.CounterInstances.Count == 1 ? category.ExportAsTransposedDataTable(false) : category.ExportAsDataTable(false, false);
            var adapter = new DataReaderDataTableAdapter(table);
            HtmlExportHelper.WriteTableHeader(writer, adapter, true, category.CategoryName, "text-align:left");
            HtmlExportHelper.WriteRowsHtml(writer, adapter, true);
            writer.Write("</tbody></table><br/>");
        }

        #endregion Methods
    }
}